package com.itheima.mp.service.impl;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.collection.CollUtil;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.baomidou.mybatisplus.extension.toolkit.Db;
import com.itheima.mp.domain.dto.PageDTO;
import com.itheima.mp.domain.po.Address;
import com.itheima.mp.domain.po.User;
import com.itheima.mp.domain.query.PageQuery;
import com.itheima.mp.domain.query.UserQuery;
import com.itheima.mp.domain.vo.AddressVO;
import com.itheima.mp.domain.vo.UserVO;
import com.itheima.mp.enums.UserStatus;
import com.itheima.mp.mapper.UserMapper;
import com.itheima.mp.service.UserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

@Service
public class UserServiceImpl extends ServiceImpl<UserMapper, User> implements UserService {
    @Autowired
    private UserMapper userMapper;


    @Override
    public void updateUserByIdAndBalance(Long id, Integer money) {
        //判断id对应的用户是否存在
        User user = userMapper.selectById(id);
        if (user == null) {
            throw new RuntimeException("用户不存在");
        }
        //判断用户状态
        if (user.getStatus() == UserStatus.FROZEN) {
            throw new RuntimeException("用户已冻结");
        }
        //判断余额是否充足
        if (user.getBalance() < money) {
            throw new RuntimeException("余额不足");
        }

//        QueryWrapper<User> queryWrapper = new QueryWrapper<>();
//        queryWrapper.eq("id", id);
//        userMapper.updateUserByIdAndBalance(queryWrapper, money);
        Integer remainMoney = user.getBalance() - money;
        lambdaUpdate().set(User::getBalance, remainMoney)
                .set(user.getBalance() == 0, User::getStatus, 2)
                .eq(User::getBalance, user.getBalance()) // 乐观锁 先比较后赋值
                .eq(User::getId, id)
                .update();
    }

    @Override
    public List<User> queryUserList(UserQuery userQuery) {
        return lambdaQuery().like(userQuery.getName() != null, User::getUsername, userQuery.getName())
                .eq(userQuery.getStatus() != null, User::getStatus, userQuery.getStatus())
                .ge(userQuery.getMinBalance() != null, User::getBalance, userQuery.getMinBalance())
                .le(userQuery.getMaxBalance() != null, User::getBalance, userQuery.getMaxBalance())
                .list();
    }

    @Override
    public UserVO getUserAndAddressById(Long id) {
        // 查询用户
        User user = getById(id);
        //判断用户信息是否存在，是否为冻结状态
        if (user == null || user.getStatus() == UserStatus.FROZEN) {
            throw new RuntimeException("用户状态不正常");
        }

        // 查询地址
        List<Address> list = Db.lambdaQuery(Address.class).eq(Address::getUserId, id).list();
        UserVO userVO = BeanUtil.copyProperties(user, UserVO.class);
        if (CollUtil.isNotEmpty(list)) {
            List<AddressVO> addressVOS = BeanUtil.copyToList(list, AddressVO.class);
            userVO.setAddresses(addressVOS);
        }
        return userVO;
    }

    @Override
    public List<UserVO> getUserAndAddressByIds(List<Long> ids) {
        //查询用户
        List<User> users = listByIds(ids);

        if (CollUtil.isEmpty(users)) {
            return CollUtil.newArrayList();
        }


        // 传过来的ids中有可能存在查不到对应用户的id，所以需要先过滤掉
        List<Long> userIds = users.stream().map(User::getId).collect(Collectors.toList());
        //查询地址
        List<Address> addresses = Db.lambdaQuery(Address.class).in(Address::getUserId, userIds).list();

        List<AddressVO> addressVOS = BeanUtil.copyToList(addresses, AddressVO.class);

        Map<Long, List<AddressVO>> map = new HashMap<>();
        //遍历地址集合，将地址集合根据userId进行分组
//        for (AddressVO addressVO : addressVOS) {
//            List<AddressVO> addressVOList = map.get(addressVO.getUserId());
//            if (addressVOList == null){
//                addressVOList = CollUtil.newArrayList();
//            }
//            addressVOList.add(addressVO);
//            map.put(addressVO.getUserId(), addressVOList);
//        }
        if (CollUtil.isNotEmpty(addressVOS)) {
            map = addressVOS.stream().collect(Collectors.groupingBy(AddressVO::getUserId));
        }

        ArrayList<UserVO> userVOS = new ArrayList<>(users.size());
        for (User user : users) {
            UserVO userVO = BeanUtil.copyProperties(user, UserVO.class);
            userVO.setAddresses(map.get(user.getId()));
            userVOS.add(userVO);
        }


        return userVOS;
    }

    @Override
    public PageDTO<UserVO> queryUserPage(PageQuery pageQuery) {

        Long pageNo = pageQuery.getPageNo();
        Long pageSize = pageQuery.getPageSize();
        if (pageNo == null || pageSize == null){
            return new PageDTO<UserVO>(0L,0L,new ArrayList<UserVO>());
        }

        String sortBy = pageQuery.getSortBy();
        Boolean isAsc = pageQuery.getIsAsc();
        // 1.构建查询条件

        Page<User> userPage = pageQuery.toMpPage(sortBy, isAsc);

        // 2.查询
        userPage = lambdaQuery().page(userPage);
        // 3.数据非空校验
        return PageDTO.of(userPage, UserVO.class);
    }
}
